﻿using Jayden.Dll.Sc2;
using Jayden.Dll.Sc2.Descriptions;
using Jayden.Dll.Web.Enums;
using Jayden.Dll.Web.HtmlControls;

namespace Jayden.Dll.Web.Controls.Sc2
{
	public class BuildOrderTable : DataTable<ActionDescription>
	{

		private GameState m_State;

		public void Clear()
		{
			base.Clear();
			m_State = null;
		}

		public override void Load(System.Xml.XmlNode node, HtmlControlLoader loader)
		{
			base.Load(node, loader);

			AddColumn(null, 20, delegate(ActionDescription action, Column column, int index) { return OneControl(new Input(HtmlInputType.Checkbox, "actionIndexes", (m_State.ActionList.Count - 1).ToString())); }, null);
			AddColumn("#", 20, delegate(ActionDescription action, Column column, int index) { return ParseText(m_State.ActionList.Count.ToString() + "."); }, null);
			AddColumn("Time", 50, delegate(ActionDescription action, Column column, int index) { return ParseText(m_State.TimeString); }, null);
			AddColumn(null, 32, delegate(ActionDescription action, Column column, int index) { return OneControl(new Img(action.IconId, "/Images/Icons/Sc2/" + action.IconId + ".gif") { Title = action.Name, Class = "icon" }); }, null);
			AddColumn("Action", 200, delegate(ActionDescription action, Column column, int index) { return ParseText(action.Name); }, null);
			AddColumn("Mineral", 50, delegate(ActionDescription action, Column column, int index) { return ParseText(((int)m_State.Mineral).ToString()); }, null);
			AddColumn("Vespene", 50, delegate(ActionDescription action, Column column, int index) { return ParseText(((int)m_State.Vespene).ToString()); }, null);
			AddColumn("Supply", 100, delegate(ActionDescription action, Column column, int index) { return ParseText(m_State.FoodUsed.ToString() + "/" + (m_State.FoodUsed + m_State.Food).ToString()); }, null);

			if (Id == null)
				Id = "buildOrderTable";
		}

		public override void ProcessJsRequest(HttpHandlerContext context)
		{
			base.ProcessJsRequest(context);

			context.Js[Id].AppendOnInit(@"
		var $table = $('#" + Id + @"');
		var $draggedRow = null;
		var $destinationRow = null;
		var startPos = null;
		var startOfst = null;
		var startIndex = null;
		var startDragFunc = function(e) {
			// avoid moving header
			if(this.cells[0].tagName === 'TH')
				return;
			$draggedRow = $(this);
			$table.addClass('noselect');
			$(window).mousemove(moveDragFunc).mouseup(endDragFunc);

			startPos = {
				x: e.pageX,
				y: e.pageY
			};
			startIndex = $draggedRow[0].rowIndex;
		};
		var endDragFunc = function() {
			$table.removeClass('noselect')
			$(window).unbind('mouseup', endDragFunc).unbind('mousemove', moveDragFunc);
			startIndex = null;
			startPos = null;
			startOfst = null;
		};
		var moveDragFunc = function(e) {
			var curPos = {
				x: e.pageX,
				y: e.pageY
			};
			var minDist = 999999;
			var best = null;
			$('tr', $table).each(function() {
				if(this.cells[0].tagName === 'TH')
					return;
				var ofst = $(this).offset();
				var distance = Math.abs(ofst.top + ($(this).height() / 2) - curPos.y);
				if(minDist > distance) {
					minDist = distance;
					best = this;
				}
			});
			var dy = curPos.y - startPos.y;
			if(best != null) {
				$destinationRow = $(best);
				if(best !== $draggedRow[0]) {
					if($draggedRow[0].rowIndex < best.rowIndex)
						$draggedRow.before($destinationRow);
					else
						$draggedRow.after($destinationRow);
				}
			}
		};
		$table.on('mousedown', 'tr', startDragFunc);
");
		}

		public new Tr AddTr(ActionDescription action)
		{
			if (m_State == null)
				m_State = new GameState(action.Entity.Race);
			if (m_State.Execute(action))
				return base.AddTr(action);
			return null;
		}
	}
}
